Trò chơi Pac-Man

20.583 lượt xem;
1 using System;
2 using
UnityEngine;
3 using
System.Collections;
4
5 public
class PlayerController : MonoBehaviour
6 {
7
8     
public float speed = 0.4f;
9     Vector2 _dest = Vector2.zero;
10     Vector2 _dir = Vector2.zero;
11     Vector2 _nextDir = Vector2.zero;
12
13     
[Serializable]
14     
public class PointSprites
15     {
16         
public GameObject[] pointSprites;
17     }
18
19     
public PointSprites points;
20
21     
public static int killstreak = 0;
22
23     
// script handles
24     
private GameGUINavigation GUINav;
25     
private GameManager GM;
26     
private ScoreManager SM;
27
28     
private bool _deadPlaying = false;
29
30     
// Use this for initialization
31     
void Start()
32     {
33         GM = GameObject.Find(
"Game Manager").GetComponent<GameManager>();
34         SM = GameObject.Find(
"Game Manager").GetComponent<ScoreManager>();
35         GUINav = GameObject.Find(
"UI Manager").GetComponent<GameGUINavigation>();
36         _dest = transform.position;
37     }
38
39     
// Update is called once per frame
40     
void FixedUpdate()
41     {
42         
switch (GameManager.gameState)
43         {
44             
case GameManager.GameState.Game:
45                 ReadInputAndMove();
46                 Animate();
47                 
break;
48
49             
case GameManager.GameState.Dead:
50                 
if (!_deadPlaying)
51                     StartCoroutine(
"PlayDeadAnimation");
52                 
break;
53         }
54
55
56     }
57
58     IEnumerator PlayDeadAnimation()
59     {
60         _deadPlaying =
true;
61         GetComponent<Animator>().SetBool(
"Die", true);
62         
yield return new WaitForSeconds(1);
63         GetComponent<Animator>().SetBool(
"Die", false);
64         _deadPlaying =
false;
65
66         
if (GameManager.lives <= 0)
67         {
68             Debug.Log(
"Treshold for High Score: " + SM.LowestHigh());
69             
if (GameManager.score >= SM.LowestHigh())
70                 GUINav.getScoresMenu();
71             
else
72                 GUINav.H_ShowGameOverScreen();
73         }
74
75         
else
76             GM.ResetScene();
77     }
78
79     
void Animate()
80     {
81         Vector2 dir = _dest - (Vector2)transform.position;
82         GetComponent<Animator>().SetFloat(
"DirX", dir.x);
83         GetComponent<Animator>().SetFloat(
"DirY", dir.y);
84     }
85
86     
bool Valid(Vector2 direction)
87     {
88         
// cast line from 'next to pacman' to pacman
89         
// not from directly the center of next tile but just a little further from center of next tile
90         Vector2 pos = transform.position;
91         direction +=
new Vector2(direction.x * 0.45f, direction.y * 0.45f);
92         RaycastHit2D hit = Physics2D.Linecast(pos + direction, pos);
93         
return hit.collider.name == "pacdot" || (hit.collider == GetComponent<Collider2D>());
94     }
95
96     
public void ResetDestination()
97     {
98         _dest =
new Vector2(15f, 11f);
99         GetComponent<Animator>().SetFloat(
"DirX", 1);
100         GetComponent<Animator>().SetFloat(
"DirY", 0);
101     }
102
103     
void ReadInputAndMove()
104     {
105         
// move closer to destination
106         Vector2 p = Vector2.MoveTowards(transform.position, _dest, speed);
107         GetComponent<Rigidbody2D>().MovePosition(p);
108
109         
// get the next direction from keyboard
110         
if (Input.GetAxis("Horizontal") > 0) _nextDir = Vector2.right;
111         
if (Input.GetAxis("Horizontal") < 0) _nextDir = -Vector2.right;
112         
if (Input.GetAxis("Vertical") > 0) _nextDir = Vector2.up;
113         
if (Input.GetAxis("Vertical") < 0) _nextDir = -Vector2.up;
114
115         
// if pacman is in the center of a tile
116         
if (Vector2.Distance(_dest, transform.position) < 0.00001f)
117         {
118             
if (Valid(_nextDir))
119             {
120                 _dest = (Vector2)transform.position + _nextDir;
121                 _dir = _nextDir;
122             }
123             
else // if next direction is not valid
124             {
125                 
if (Valid(_dir)) // and the prev. direction is valid
126                     _dest = (Vector2)transform.position + _dir;
// continue on that direction
127
128                 
// otherwise, do nothing
129             }
130         }
131     }
132
133     
public Vector2 getDir()
134     {
135         
return _dir;
136     }
137
138     
public void UpdateScore()
139     {
140         killstreak++;
141
142         
// limit killstreak at 4
143         
if (killstreak > 4) killstreak = 4;
144
145         Instantiate(points.pointSprites[killstreak -
1], transform.position, Quaternion.identity);
146         GameManager.score += (
int)Mathf.Pow(2, killstreak) * 100;
147
148     }
149 }


script handles

Use this for initialization

Update is called once per frame

cast line from 'next to pacman' to pacman

not from directly the center of next tile but just a little further from center of next tile

move closer to destination

get the next direction from keyboard

if pacman is in the center of a tile

else if next direction is not valid

if (Valid(_dir)) and the prev. direction is valid

_dest = (Vector2)transform.position + _dir; continue on that direction

otherwise, do nothing

limit killstreak at 4



Gõ tìm kiếm nhanh...